import os
import platform
import random
import logging
import json
import subprocess
import time

import yaml

from src.common.prj_path import get_abs_path

LOG = logging.getLogger()


def input_time_random():
    return random.randint(50, 100)


def write_file(path, content, json_flag=False):
    try:
        with open(path, 'w') as f:
            if json_flag:
                json.dump(content, f, indent=4)
            else:
                f.write(content)
    except Exception as e:
        err_msg = 'write {}, error={}, content={}'.format(path, e, content)
        LOG.error(err_msg)
        raise Exception(err_msg)


def read_file(path, json_flag=False):
    try:
        with open(path, 'r', encoding='UTF-8') as f:
            if json_flag:
                return json.load(f)
            else:
                return f.read()
    except Exception as e:
        err_msg = 'read {}, error={}'.format(path, e)
        LOG.error(err_msg)
        raise Exception(err_msg)


def get_execute_cmd_result(cmd):
    try:
        LOG.debug("execute cmd={}".format(cmd))
        p = subprocess.check_output(cmd, stderr=subprocess.STDOUT, shell=True)
        return bytes.decode(p).strip()
    except Exception as e:
        err_msg = "execute cmd failed, cmd={}, error={}".format(cmd, e)
        LOG.warning(err_msg)
        raise Exception(err_msg)


def get_platform_name():
    name = platform.system()
    name = name.lower()
    if name not in ['windows', 'linux']:
        err_msg = 'not support this platform={}'.format(name)
        LOG.error(err_msg)
        raise Exception(err_msg)
    LOG.debug('now platform system is {}'.format(name))
    return name


def read_yaml(path):
    try:
        with open(path, 'r', encoding='utf-8') as f:
            result = f.read()
        yaml_dict = yaml.safe_load(result)
        return yaml_dict
    except Exception as e:
        err_msg = 'read {} failed, error={}'.format(path, e)
        LOG.warning(err_msg)
        raise Exception(err_msg)


class MyTime(object):
    @staticmethod
    def timestamp() -> float:
        return time.time()

    @staticmethod
    def format_date_time_1() -> str:
        return time.strftime("%Y-%m-%d_%H-%M-%S", time.localtime())

    @staticmethod
    def format_date_time_2() -> str:
        return time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())

    @staticmethod
    def time_difference(start_time: float) -> float:
        if start_time > 1600000000:
            raise Exception('time_difference input param must be time.perf_counter()')
        return time.perf_counter() - start_time


class MyPath():
    @staticmethod
    def make_dirs_if_not_exist(path: str):
        if not os.path.exists(path):
            os.makedirs(path)

    @staticmethod
    def basename(path: str) -> str:
        return os.path.basename(path)


def run_self_func_args(func, args: str):
    func_name = getattr(func, '__name__')
    param_num = func.__code__.co_argcount
    if param_num < 1:
        err_msg = "run_self_func_args: {} must be self.func".format(func_name)
        LOG.error(err_msg)
        raise Exception(err_msg)
    param_num -= 1
    err_msg = '{} args number is not correct, args={}, param_num={}'.format(func_name, args, param_num)
    if args and param_num > 0:
        if not isinstance(args, str):
            return func(args)
        args_list = args.split('|')
        if param_num != len(args_list):
            LOG.error(err_msg)
            raise Exception(err_msg)
        elif param_num == 1:
            return func(args)
        else:
            return func(*args_list)
    elif not args and param_num == 0:
        return func()
    else:
        LOG.error(err_msg)
        raise Exception(err_msg)


def get_bounds_center(coord):
    x_point = (int(coord[2]) - int(coord[0])) / 2.0 + int(coord[0])
    y_point = (int(coord[3]) - int(coord[1])) / 2.0 + int(coord[1])
    return x_point, y_point


def check_str_equal(str1: str, str2: str, match_case=True) -> bool:
    if match_case:
        return str1 == str2
    else:
        return str1.lower() == str2.lower()


if __name__ == '__main__':
    path = get_abs_path('1', '2', '111.3')
    print(os.path.dirname(path))
